package org.aeon.gamechatnest.validated.validator;

import jakarta.validation.ConstraintValidator;
import jakarta.validation.ConstraintValidatorContext;
import lombok.SneakyThrows;
import org.aeon.gamechatnest.validated.annotation.AnyNotEmpty;
import org.hibernate.validator.internal.engine.constraintvalidation.ConstraintValidatorContextImpl;

import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;

/**
 * @author: MissingAeon
 * @date: 2024/5/10 13:16
 * @description:
 */
public class AnyNotEmptyValidator implements ConstraintValidator<AnyNotEmpty, Object> {

    private final Map<String, Boolean> initialField = new HashMap<>();
    private Map<String, Boolean> limitedField;

    @Override
    public void initialize(AnyNotEmpty constraintAnnotation) {
        Field[] fields = constraintAnnotation.clazz().getDeclaredFields();
        for (Field field : fields) {
            AnyNotEmpty annotation = field.getAnnotation(AnyNotEmpty.class);
            if (annotation != null) {
                if (field.getAnnotation(AnyNotEmpty.class).value() == constraintAnnotation.value()) {
                    initialField.put(field.getName(), null);
                }
            }
        }
        limitedField = new HashMap<>(initialField);
    }

    @SneakyThrows
    @Override
    public boolean isValid(Object value, ConstraintValidatorContext context) {
        limitedField.put(((ConstraintValidatorContextImpl) context).getConstraintViolationCreationContexts().get(0)
                .getPath().asString(), value != null);
        // 判断
        boolean b = limitedField.values().stream().anyMatch(Objects::isNull);
        if (b) {
            return true;
        }
        b = limitedField.values().stream().anyMatch(Boolean::booleanValue);
        limitedField = new HashMap<>(initialField);
        return b;
    }
}
